package com.bjpowernode.springboot.controller;

import com.bjpowernode.springboot.entity.User;
import com.bjpowernode.springboot.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.servlet.ModelAndView;

import javax.jws.WebParam;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;

/**
 * 操作User的Controller层，主要实现一下的操作
 * 1. 用户的登录操作
 * 2. 用户的注册操作
 * 3. 测试连接的方法
 */
@SuppressWarnings("all")
@Controller
@RequestMapping("/user")
public class UserController {

    @Value("${login-info}")
    private String LOGIN_INFO;

    @Value("${login-error}")
    private String LOGIN_ERROR;

    @Value("${register-info}")
    private String REGISTER_INFO;

    @Value("${register-error}")
    private String REGISTER_ERROR;


    @Autowired
    private UserService userService; // 注入service层的对象，实现对应的操作


    @RequestMapping("/gate")
    public String gate() {
        return "User";
    }


    /**
     * 进入登录页面
     * @return
     */
    @RequestMapping("/login")
    public String login() {
        return "UserLogin";
    }

    /**
     * 进入注册页面
     * @return
     */
    @RequestMapping("/register")
    public String register() {
        return "UserRegister";
    }

    /**
     * 使用用户的登录操作
     * 1. 判断当前用户是否已经登录，如果已经登陆直接跳转到实际网页（这一步就是看当前的用户是否在redis缓存中）
     * 2. 当前用户没有登陆，进行登陆操作
     * 3. 将用户的登陆信息封装到session中，然后放进redis缓存，并设置一个过期时间，一旦过期，该数据自动从redis缓存中移除
     * @param request
     * @return
     */
    @RequestMapping("/do-login")
    public ModelAndView doLogin(HttpServletRequest request) {
        ModelAndView mv = new ModelAndView();
        // 获取用户输入的用户名和密码
        String username = request.getParameter("username");
        String password = request.getParameter("password");
        // 封装对象
        User user = new User();
        packUser(user,username,password);
        // 判断当前的用户是否已经在缓存中，如果在表明之前已经登录过，用户点击登录直接显示页面
        // 否则从数据库中获取数据进行匹配，如果没有匹配到，跳转到注册页面进行注册，如果匹配到
        // 跳转到登录之后的页面
        boolean isLogin = userService.isReadyLogin(user);
        if (isLogin) {
            mv.addObject("login-info","欢迎用户" + username + "访问");
            mv.setViewName("login-success");
            return mv;
        }
        // 没有登录，登录
        // 判断用户输入是否为空，或者输入是否满足用户名和密码规则
        if (username == null || password == null) {
            mv = checkNull(mv,username,password,LOGIN_ERROR,"输入不能为空, 请重新输入","login-error");
            return mv;
        }

        if (Character.isDigit(username.charAt(0)) || username.length() > 10 || !username.matches("[a-zA-Z0-9]+")) {
            mv = checkUserNamePattern(mv,username, LOGIN_ERROR,"输入的用户名根式不正确，请重新输入","login-error");
            return mv;
        }

        if (password.length() > 12 || password.length() < 8 || password.matches("[0-9]+") || password.matches("[a-zA-Z]+")) {
            mv = checkPasswordPattern(mv,password, LOGIN_ERROR,"输入的密码根式不正确，请重新输入","login-error");
            return mv;
        }

        // 输入没有格式问题
        // 将当前的用户信息和数据库进行匹配
        User queryUser = userService.isUserExist(user);
        if (queryUser == null) {
            // 如果用户不在数据库中，跳转到注册页面进行注册
            mv.addObject("info","您还未注册，请先注册在登录");
            mv.setViewName("forward-register"); // 跳转页面
            return mv;
        }
        // 用户存在，表明已经注册，将用户存放到session之后放入redis缓存中
        HttpSession session = request.getSession(); // 获取session对象
        session.setAttribute("username",username);
        session.setAttribute("password",password);
        session.setAttribute("sessionId",queryUser.getId());
        userService.cacheSaveUser(session); // 将session缓存到redis中
        mv.addObject("login-info","欢迎用户" + username + "访问");
        mv.setViewName("login-success");
        return mv;
    }

    /**
     * 用户的注册操作
     * @param request
     * @return
     */
    @RequestMapping("/do-register")
    public ModelAndView doRegister(HttpServletRequest request) {
        ModelAndView mv = new ModelAndView();
        String username = request.getParameter("username");
        String password = request.getParameter("password");
        // 判断输入是否为空或者输入的格式是否正确
        if (username == null || password == null) {
            mv = checkNull(mv,username,password,REGISTER_ERROR,"输入不能为空, 请重新输入","register-error");
            return mv;
        }

        if (Character.isDigit(username.charAt(0)) || username.length() > 10 || !username.matches("[a-zA-Z0-9]+")) {
            mv = checkUserNamePattern(mv,username, REGISTER_ERROR,"输入的用户名根式不正确，请重新输入","register-error");
            return mv;
        }

        if (password.length() > 12 || password.length() < 8 || password.matches("[0-9]+") || password.matches("[a-zA-Z]+")) {
            mv = checkPasswordPattern(mv,password, REGISTER_ERROR,"输入的密码根式不正确，请重新输入","register-error");
            return mv;
        }
        // 输入不为空，并且格式正确，注册
        // 封装用户
        User user = new User();
        packUser(user,username,password);
        // 将用户信息保存到数据库中
        userService.addUser(user);
        mv.addObject(REGISTER_INFO,"注册成功，现在帮您跳转到登录页面，请稍后...");
        mv.setViewName("UserLogin");
        return mv;
    }

    /**
     * 判断用户输入是否为空
     * @param mv：封装最终的视图对象
     * @param username
     * @param password
     * @param feedback：反馈到页面的信息
     * @param forward：反馈信息的页面路径
     * @return
     */
    public ModelAndView checkNull(ModelAndView mv, String username, String type, String password, String feedback, String forward) {
        if (username == null || password == null) {
            mv.addObject(type,feedback);
            mv.setViewName(forward);
        }
        return mv;
    }

    /**
     * 验证用户名格式
     * @param mv
     * @param username
     * @param feeback
     * @param forward
     * @return
     */
    public ModelAndView checkUserNamePattern(ModelAndView mv, String username, String type, String feeback, String forward) {
        int len = username.length();
        if(Character.isDigit(username.charAt(0)) || len > 10 || !username.matches("[0-9a-zA-Z]+")) {
            mv.addObject(type,feeback);
            mv.setViewName(forward);
        }
        return mv;
    }


    /**
     * 验证密码格式
     * @param mv
     * @param password
     * @param feedback
     * @param forward
     * @return
     */
    public ModelAndView checkPasswordPattern(ModelAndView mv , String password, String type, String feedback, String forward) {
        int len = password.length();
        if (len < 8 || len > 12 || password.matches("[0-9]+") || password.matches("[a-zA-Z]+")) {
            mv.addObject(type,feedback);
            mv.setViewName(forward);
        }
        return mv;
    }



    /**
     * 封装User对象
     * @param user
     * @param username
     * @param password
     */
    public void packUser(User user, String username, String password) {
        user.setUsername(username);
        user.setPassword(password);
    }










    /*++++++++++++++++++++++++++++++++++++++++++++测试+++++++++++++++++++++++++++++++++++++++++++*/
    /**
     * 测试连接
     * @return
     */
    @RequestMapping("/test")
    public String test_connect() {
        return "test";
    }

    /**
     * 测试参数接受
     * 抛出异常：Error resolving template [user/do-test], template might not exist or
     *          might not be accessible by any of the configured Template Resolvers
     * 原因：之前该方法并没有添加注解@ResponseBody，则虽然返回值为空，但是thmyleaf模板引擎也会将
     * 其解析为页面，但是此时并没有任何页面解析，所以抛出异常
     * 所以只需要添加上@ResponseBody，此时就需要通过thmyleaf来解析
     * @param request
     */
    @RequestMapping("/do-test")
    @ResponseBody
    public void doTest(HttpServletRequest request) {
        String username = request.getParameter("username");
        System.out.println(username);
    }

}
